package top.boking.action;

import com.alibaba.fastjson.JSONObject;

import org.apache.commons.lang3.StringUtils;
import org.apache.http.HttpEntity;
import org.apache.http.NameValuePair;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;


import javax.rmi.CORBA.Util;
import java.io.IOException;
import java.nio.charset.Charset;
import java.util.*;

/**
 * @version: V1.0
 * @Description: e-Builder openApi Demo
 * @description: 泛微协同商务系统, 版权所有.
 */
public class RestfulDemo {

    public static void main(String[] args) {
        String accessToken = getAccessToken();
        RestfulDemo restfulDemo = new RestfulDemo();
        String result = restfulDemo.doAction(accessToken);
        System.out.println(result);
    }


    /**
     * e-Builder openApi Demo
     * ex:getFormDataList
     * @param accessToken
     */
    public String doAction(String accessToken) {
        CloseableHttpClient httpClient = HttpClients.createDefault();
        HttpPost httpPost = new HttpPost("https://api.eteams.cn/api/ebuilder/form/formdata/getFormDataList/i7b084?access_token=" + accessToken);
        JSONObject params = new JSONObject();
        JSONObject paramDatajson = new JSONObject();

        //header
        JSONObject header = new JSONObject();
        String operator = "5112849484828049659";
        header.put("operator", operator);
        paramDatajson.put("header", header);

        //pageinfo
        JSONObject pageInfo = new JSONObject();
        pageInfo.put("pageNo", 1);
        pageInfo.put("pageSize", 5);
        paramDatajson.put("pageInfo", pageInfo);

        //mainTable
        JSONObject mainTable = new JSONObject();
        mainTable.put("id", "719110733949992960");
        paramDatajson.put("mainTable", mainTable);

        //operationinfo
        JSONObject operationinfo = new JSONObject();
        paramDatajson.put("operationinfo", operationinfo);

        params.put("datajson", paramDatajson);

        System.out.println("===request datajson===" + paramDatajson);

        List nvps = new ArrayList();
        if (params != null) {
            for (Map.Entry entry : params.entrySet()) {
                String key = "";
                if (entry.getKey() != null) {
                    key = entry.getKey().toString();
                }
                nvps.add(new BasicNameValuePair(key, JSONObject.toJSONString(entry.getValue())));
            }
        }
        try {
            UrlEncodedFormEntity reqEntity = new UrlEncodedFormEntity(nvps, "utf-8");
            httpPost.setEntity(reqEntity);
            // exec post request.
            CloseableHttpResponse response = httpClient.execute(httpPost);
            try {
                int statusCode = response.getStatusLine().getStatusCode();
                if (statusCode != 200) {
                    System.out.println("request failed");
                    throw new RuntimeException("request failed");
                } else {
                    HttpEntity entity = response.getEntity();
                    if (entity != null) {
                        System.out.println("request success");
                        return EntityUtils.toString(entity, Charset.forName("UTF-8"));
                    }
                }
            } finally {
                response.close();
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return "";

    }


    /**
     * Get authorization code
     *
     * @return authorizeCode
     */
    public static String getAuthorizeCode() {
        // Authorized address
        String url = "https://api.eteams.cn/oauth2/authorize";

        Map reqParam = new HashMap<>();
        // Registered company corp Id
        reqParam.put("corpid", "6caeb52680ecddf055e83508c2f84371");
        // The return type is fixed : code
        reqParam.put("response_type", "code");
        // After the redirection, the state parameter will be brought. The enterprise can fill in the parameter value of a-z A-Z 0-9, and the length cannot exceed 128 bytes.
        reqParam.put("state", "123123");
        try {
            String authorizeCode = post(url, reqParam);
            if (StringUtils.isNotBlank(authorizeCode)) {
                JSONObject authorizeCodeObj = JSONObject.parseObject(authorizeCode);
                return null2String(authorizeCodeObj.get("code"));
            } else {
                new Exception("authorizeCode generate exception");
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return "";
    }


    public static String getAccessToken() {
        // Authorized address
        String url = "https://api.eteams.cn/oauth2/access_token";
        // get authorizeCode
        String authorizeCode = getAuthorizeCode();
        Map reqParam = new HashMap<>();
        reqParam.put("app_key", "c31767f0f4700bf6b098cdaafe2b5ac6");
        reqParam.put("app_secret", "53c2e529b572fc250b83748bee2afea5");
        reqParam.put("grant_type", "authorization_code");
        reqParam.put("code", authorizeCode);
        try {
            String accessToken = post(url, reqParam);
            if (StringUtils.isNotBlank(accessToken)) {
                JSONObject accessTokenObj = JSONObject.parseObject(accessToken);
                return null2String(accessTokenObj.get("accessToken"));
            } else {
                new Exception("accessToken generate exception");
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return "";
    }


    /**
     * send request
     *
     * @param url
     * @param reqParam
     * @return
     * @throws Exception
     */
    public static String post(String url, Map<Object,Map.Entry> reqParam) throws Exception {
        CloseableHttpClient httpclient = HttpClients.createDefault();
        try {
            // create httppost.
            HttpPost httppost = new HttpPost(url);
            httppost.setHeader("Content-Type", "application/x-www-form-urlencoded");
            List nvps = new ArrayList();
            if (reqParam != null) {
                for (Map.Entry entry : reqParam.entrySet()) {
                    nvps.add(new BasicNameValuePair((String) entry.getKey(), (String) entry.getValue()));
                }
            }
            UrlEncodedFormEntity reqEntity = new UrlEncodedFormEntity(nvps, "utf-8");
            httppost.setEntity(reqEntity);
            CloseableHttpResponse response = httpclient.execute(httppost);
            try {
                int statusCode = response.getStatusLine().getStatusCode();
                if (statusCode != 200) {
                    throw new RuntimeException("request failed");
                } else {
                    HttpEntity entity = response.getEntity();
                    if (entity != null) {
                        return EntityUtils.toString(entity, Charset.forName("UTF-8"));
                    }
                }
            } finally {
                response.close();
            }
        } finally {
            try {
                httpclient.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return null;
    }


    public static String null2String(Object s) {
        return s == null ? "" : s.toString();
    }

}
